#include "cargarImagenes.h"

using namespace std;
float L=1;

vector<float> b;
Matriz A;

float auxcalcular(float pixel, float pixelU, float pixelD, float pixelL, float pixelR)
{

//    cout << "Pixel:" << pixel << endl;
//    cout << "U:" << pixelU << endl;
//    cout << "D:" << pixelD << endl;
//    cout << "L:" << pixelL << endl;
//    cout << "R:" << pixelR << endl<<endl;

    return (L*pixel + pixelU + pixelD + pixelL + pixelR);
}

void cargarMatrices(FILE * imagen, int ancho, int alto)
{
    float  pixelU, pixelD, pixelR, pixelL;

    /// Guardo la posicion donde comienza la imagen.
    fpos_t initial_position;
    fgetpos(imagen, &initial_position);

    Foto foto;
    foto.guardarImagen(imagen);
    fsetpos (imagen, &initial_position);
    for(int i=0; i<alto; i++)
    {
        for(int j=0; j< ancho; j++)         /// Levanto el pixel actual sin moverme de la posicion.
        {
            if (i == 0)  /// Arriba de todo.
            {
                if (j == 0) /// Izquierda de todo.
                {
                    pixelU = (foto[i][j+1] + foto[i][j])/2;
                    pixelL = (foto[i+1][j] + foto[i][j])/2;
                    pixelD = 0;
                    pixelR = 0;
                    A.set(1+i*ancho+j,1+i*ancho+j,L+4);     /// (L+4), pos del pixel
                    A.set(1+i*ancho+j,2+i*ancho+j,-1);      /// -1   , pos de la der
                    A.set(1+i*ancho+j,(i+1)*ancho+j+1,-1);    /// -1   , pos de la abajo
                }
                else if (j == ancho - 1) /// Derecha de todo.
                {
                    pixelU = (foto[i][j-1] + foto[i][j])/2;
                    pixelR = (foto[i+1][j] + foto[i][j])/2;
                    pixelD = 0;
                    pixelL = 0;
                    A.set(1+i*ancho+j,1+i*ancho+j,L+4);     /// (L+4), pos del pixel
                    A.set(1+i*ancho+j,i*ancho+j,-1);        /// -1   , pos de la izq
                    A.set(1+i*ancho+j,(i+1)*ancho+j+1,-1);    /// -1   , pos de la abajo
                }
                else /// En el diome.
                {
                    pixelU = (foto[i][j-1] + foto[i][j] + foto[i][j+1])/3;
                    pixelL = 0;
                    pixelD = 0;
                    pixelR = 0;
                    A.set(1+i*ancho+j,1+i*ancho+j,L+4);     /// (L+4), pos del pixel
                    A.set(1+i*ancho+j,i*ancho+j,-1);        /// -1   , pos de la izq
                    A.set(1+i*ancho+j,2+i*ancho+j,-1);      /// -1   , pos de la der
                    A.set(1+i*ancho+j,(i+1)*ancho+j+1,-1);    /// -1   , pos de la abajo
                }
            }
            else if (i == alto - 1) /// Abajo de todo.
            {
                if (j == 0) /// Izquierda de todo.
                {
                    pixelD = (foto[i][j+1] + foto[i][j])/2;
                    pixelL = (foto[i-1][j] + foto[i][j])/2;
                    pixelU = 0;
                    pixelR = 0;
                    A.set(1+i*ancho+j,1+i*ancho+j,L+4);     /// (L+4), pos del pixel
                    A.set(1+i*ancho+j,2+i*ancho+j,-1);      /// -1   , pos de la der
                    A.set(1+i*ancho+j,1+(i-1)*ancho+j,-1);  /// -1   , pos de la arriba
                }
                else if (j == ancho -1) /// Derecha de todo
                {
                    pixelD = (foto[i][j-1] + foto[i][j])/2;
                    pixelR = (foto[i-1][j] + foto[i][j])/2;
                    pixelU = 0;
                    pixelL = 0;
                    A.set(1+i*ancho+j,1+i*ancho+j,L+4);     /// (L+4), pos del pixel
                    A.set(1+i*ancho+j,i*ancho+j,-1);        /// -1   , pos de la izq
                    A.set(1+i*ancho+j,1+(i-1)*ancho+j,-1);  /// -1   , pos de la arriba
                }
                else /// En el diome
                {
                    pixelD = (foto[i][j-1] + foto[i][j] + foto[i][j+1])/3;
                    pixelL = 0;
                    pixelU = 0;
                    pixelR = 0;
                    A.set(1+i*ancho+j,1+i*ancho+j,L+4);     /// (L+4), pos del pixel
                    A.set(1+i*ancho+j,i*ancho+j,-1);        /// -1   , pos de la izq
                    A.set(1+i*ancho+j,2+i*ancho+j,-1);      /// -1   , pos de la der
                    A.set(1+i*ancho+j,1+(i-1)*ancho+j,-1);  /// -1   , pos de la arriba
                }
            }
            else /// En el diome
            {
                if (j == 0) /// Izquierda de todo
                {
                    pixelL = (foto[i-1][j] + foto[i][j] + foto[i+1][j])/3;
                    pixelD = 0;
                    pixelU = 0;
                    pixelR = 0;
                    A.set(1+i*ancho+j,1+i*ancho+j,L+4);     /// (L+4), pos del pixel
                    A.set(1+i*ancho+j,2+i*ancho+j,-1);      /// -1   , pos de la der
                    A.set(1+i*ancho+j,1+(i-1)*ancho+j,-1);  /// -1   , pos de la arriba
                    A.set(1+i*ancho+j,(i+1)*ancho+j+1,-1);    /// -1   , pos de la abajo
                }
                else if (j == ancho -1) /// Derecha de todo
                {
                    pixelR = (foto[i-1][j] + foto[i][j] + foto[i+1][j])/3;
                    pixelD = 0;
                    pixelU = 0;
                    pixelL = 0;
                    A.set(1+i*ancho+j,1+i*ancho+j,L+4);     /// (L+4), pos del pixel
                    A.set(1+i*ancho+j,i*ancho+j,-1);        /// -1   , pos de la izq
                    A.set(1+i*ancho+j,1+(i-1)*ancho+j,-1);  /// -1   , pos de la arriba
                    A.set(1+i*ancho+j,(i+1)*ancho+j+1,-1);    /// -1   , pos de la abajo
                }
                else /// En el diome
                {
                    pixelL = 0;
                    pixelD = 0;
                    pixelU = 0;
                    pixelR = 0;
                    A.set(1+i*ancho+j,1+i*ancho+j,L+4);     /// (L+4), pos del pixel
                    A.set(1+i*ancho+j,i*ancho+j,-1);        /// -1   , pos de la izq
                    A.set(1+i*ancho+j,2+i*ancho+j,-1);      /// -1   , pos de la der
                    A.set(1+i*ancho+j,1+(i-1)*ancho+j,-1);  /// -1   , pos de la arriba
                    A.set(1+i*ancho+j,(i+1)*ancho+j+1,-1);    /// -1   , pos de la abajo
                }
            }
            b[i*ancho +j] = auxcalcular(L*foto[i][j], pixelU,pixelD,pixelL,pixelR);
        }
    }
}


int cargarParam(FILE * imagen)
{
    char buffer[1024];
    char temp = getc(imagen);
    for(int i = 0; temp != ' '&& temp != '\n'; i++)
    {
        buffer[i] = temp;
        temp = getc(imagen);
    }
    return atoi(buffer);
}

pair<Matriz, vector<float> > crearAyB(FILE * imagen, float Lambda, FILE* destino)
{
    int ancho;
    int alto;
    L = Lambda;
    char basura [100];
    fgets(basura,100,imagen);
    cout <<"Indentifying file: "<< basura;
    fputs(basura,destino);

    fgets(basura,100,imagen);
    cout <<"Whitespace: "<< basura;
    fputs(basura,destino);

    ancho = cargarParam(imagen);
    cout <<"Width: "<< ancho << endl;

    alto = cargarParam(imagen);
    cout <<"Height: "<< alto << endl;

    stringstream ss;
    ss << ancho << " " << alto << "\n";
    char anchoyalto[100] = {};
    convertStringToArrayChar(anchoyalto, ss.str());

    /// Guardamos el ancho y el alto en la imagen nueva.
    fputs(anchoyalto,destino);

    A.Resize(alto*ancho,alto*ancho);
    b.resize(ancho*ancho);

    cout<<"TAMAÑO de B: "<<b.size()<<endl;

    fgets(basura, 5,imagen);
    cout <<"Maximum grayscale value: "<< basura << endl;
    fputs(basura,destino);

    cargarMatrices(imagen, ancho, alto);
    pair<Matriz, vector<float> > tuplaResultado (A, b);

//A.print()
    return tuplaResultado;
}


//    pepe<<"despues"<<endl;
//    for(int i=0; i<b.size(); i++)
//            pepe<< setprecision(10)<<setw(10)<<b[i]<<endl;
